﻿using Abp.Application.Services.Dto;
using Abp.Collections.Extensions;
using Abp.Domain.Repositories;
using Abp.Extensions;
using Akso.DataMaintains.Dto;
using Akso.Entities;
using System;
using System.Collections.Generic;
using System.Data.Entity;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Linq.Dynamic;
using Abp.Linq.Extensions;
using Abp.AutoMapper;
using Abp.Authorization;
using Akso.Authorization;
using System.Diagnostics;

namespace Akso.DataMaintains
{
    public class DataMaintainAppService: AbpZeroTemplateAppServiceBase, IDataMaintainAppService
    {
        private readonly IRepository<BillAccount, Guid> _billAccountsRepository;
        private readonly IRepository<IncomeExpendType, Guid> _incomeExpendTypesRepository;
        private readonly IRepository<BillOtherCheck, Guid> _otherChecksRepository;
        public DataMaintainAppService(IRepository<BillAccount, Guid> billAccountsRepository,
            IRepository<IncomeExpendType, Guid> incomeExpendTypesRepository,
            IRepository<BillOtherCheck, Guid> otherChecksRepository)
        {
            _billAccountsRepository = billAccountsRepository;
            _incomeExpendTypesRepository = incomeExpendTypesRepository;
            _otherChecksRepository = otherChecksRepository;

        }

        #region 查询数据
        /// <summary>
        /// 根据输入条件进行数据查询
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        //private IQueryable<BillAccount> getQuery(GetBillAccountsInput input)
        //{
        //    var query = _billAccountsRepository.GetAll()
        //        .WhereIf(
        //            !input.Filter.IsNullOrWhiteSpace(),
        //            t =>
        //                t.AccountName.Contains(input.Filter) ||
        //                t.Remark.Contains(input.Filter)
        //        );
        //    return query;
        //}
        public async Task<ListResultDto<BillAccountListDto>> GetBillAccounts(GetBillAccountsInput input)
        {
            var query = _billAccountsRepository.GetAll()
                .WhereIf(
                    !input.Filter.IsNullOrWhiteSpace(),
                    t =>
                        t.AccountName.Contains(input.Filter) ||
                        t.Remark.Contains(input.Filter)
                );
            var dataCount = await query.CountAsync();
            var data = await query.OrderBy(input.Sorting).PageBy(input).ToListAsync();

            return new PagedResultDto<BillAccountListDto>(
                dataCount,
                data.MapTo<List<BillAccountListDto>>()
                );
        }
        #endregion

        #region 新增、编辑对象，带权限检查
        /// <summary>
        /// 新增、编辑对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateAccount, AppPermissions.Pages_FinanceModule_DataMaintains_EditAccount)]
        public async Task<BillAccount> CreateOrUpdateBillAccount(CreateOrUpdateBillAccountInput input)
        {
            if (input.BillAccount.Id.HasValue)
            {
                return await UpdateBillAccount(input);
            }
            else
            {
                return await CreateBillAccount(input);
            }
        }

        /// <summary>
        /// 新增对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateAccount)]
        protected virtual async Task<BillAccount> CreateBillAccount(CreateOrUpdateBillAccountInput input)
        {
            var o = input.BillAccount.MapTo<BillAccount>();
           
            
            return await _billAccountsRepository.InsertAsync(o);
        }
        /// <summary>
        /// 编辑对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_EditAccount)]
        protected virtual async Task<BillAccount> UpdateBillAccount(CreateOrUpdateBillAccountInput input)
        {
            Debug.Assert(input.BillAccount.Id != null, "input.BillAccount.Id should be set.");

            var o = await _billAccountsRepository.GetAsync(input.BillAccount.Id.Value);
            //Update classroom properties
            input.BillAccount.MapTo(o);
            return await _billAccountsRepository.UpdateAsync(o);
        }
        #endregion

        #region 删除账户数据，带权限检查
        /// <summary>
        /// 删除对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_DeleteAccount)]
        public async Task DeleteBillAccount(EntityDto<Guid> input)
        {
            var o = await _billAccountsRepository.GetAsync(input.Id);
            await _billAccountsRepository.DeleteAsync(o);
        }
        #endregion

        #region 根据Guid获取数据对象
        /// <summary>
        /// 新增、编辑页面中获取对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateAccount, AppPermissions.Pages_FinanceModule_DataMaintains_EditAccount)]
        public async Task<GetBillAccountForEditOutput> GetBillAccountForEdit(NullableIdDto<Guid> input)
        {
            var output = new GetBillAccountForEditOutput
            {

            };

            if (!input.Id.HasValue)
            {
                //Creating a new object
                output.BillAccount = new BillAccountEditDto();
            }
            else
            {
                //Editing an existing object
                var existingObject = await _billAccountsRepository.GetAsync(input.Id.Value);

                output.BillAccount = existingObject.MapTo<BillAccountEditDto>();
            }

            return output;
        }
        #endregion

        #region 收支分类
        /// <summary>
        /// 查询
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        public async Task<ListResultDto<IncomeExpendTypeListDto>> GetIncomeExpendTypes(GetIncomeExpendsInput input)
        {
            var query = _incomeExpendTypesRepository.GetAll()
                .WhereIf(
                    !input.Filter.IsNullOrWhiteSpace(),
                    t =>
                        t.IETypeName.Contains(input.Filter) ||
                        t.Remark.Contains(input.Filter)
                );
            var dataCount = await query.CountAsync();
            var data = await query.OrderBy(input.Sorting).PageBy(input).ToListAsync();

            return new PagedResultDto<IncomeExpendTypeListDto>(
                dataCount,
                data.MapTo<List<IncomeExpendTypeListDto>>()
                );
        }
        #region 根据Guid获取数据收支分类对象
        /// <summary>
        /// 新增、编辑页面中获取对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateIEType, AppPermissions.Pages_FinanceModule_DataMaintains_EditIEType)]
        public async Task<GetIncomeExpendTypeForEditOutput> GetIncomeExpendTypeForEdit(NullableIdDto<Guid> input)
        {
            var output = new GetIncomeExpendTypeForEditOutput
            {

            };

            if (!input.Id.HasValue)
            {
                //Creating a new object
                output.IncomeExpendType = new IncomeExpendTypeEditDto();
            }
            else
            {
                //Editing an existing object
                var existingObject = await _incomeExpendTypesRepository.GetAsync(input.Id.Value);

                output.IncomeExpendType = existingObject.MapTo<IncomeExpendTypeEditDto>();
            }

            return output;
        }
        #endregion

        #region 删除账户数据，带权限检查
        /// <summary>
        /// 删除对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_DeleteIEType)]
        public async Task DeleteIncomeExpendType(EntityDto<Guid> input)
        {
            var o = await _incomeExpendTypesRepository.GetAsync(input.Id);
            await _incomeExpendTypesRepository.DeleteAsync(o);
        }
        #endregion

        #region 新增、编辑收支分类对象，带权限检查
        /// <summary>
        /// 新增、编辑对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateIEType, AppPermissions.Pages_FinanceModule_DataMaintains_EditIEType)]
        public async Task<IncomeExpendType> CreateOrUpdateIncomeExpendType(CreateOrUpdateIncomeExpendTypeInput input)
        {
            if (input.IncomeExpendType.Id.HasValue)
            {
                return await UpdateIncomeExpendType(input);
            }
            else
            {
                return await CreateIncomeExpendType(input);
            }
        }

        /// <summary>
        /// 新增对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateIEType)]
        protected virtual async Task<IncomeExpendType> CreateIncomeExpendType(CreateOrUpdateIncomeExpendTypeInput input)
        {
            var o = input.IncomeExpendType.MapTo<IncomeExpendType>();


            return await _incomeExpendTypesRepository.InsertAsync(o);
        }
        /// <summary>
        /// 编辑对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_EditIEType)]
        protected virtual async Task<IncomeExpendType> UpdateIncomeExpendType(CreateOrUpdateIncomeExpendTypeInput input)
        {
            Debug.Assert(input.IncomeExpendType.Id != null, "input.IncomeExpendType.Id should be set.");

            var o = await _incomeExpendTypesRepository.GetAsync(input.IncomeExpendType.Id.Value);
            //Update classroom properties
            input.IncomeExpendType.MapTo(o);
            return await _incomeExpendTypesRepository.UpdateAsync(o);
        }
        #endregion
        #endregion

        /// <summary>
        /// 获取收支分了下拉框列表
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        public ListResultDto<IncomeExpendTypeListDto> GetListIncomeExpendTypes(int input)
        {

            var ieTypeList = _incomeExpendTypesRepository.GetAll().Where(x => x.IETypeId == input).ToList();
            return new ListResultDto<IncomeExpendTypeListDto>(ieTypeList.MapTo<List<IncomeExpendTypeListDto>>());
        }
        /// <summary>
        /// 获取账户
        /// </summary>
        /// <returns></returns>
        public ListResultDto<BillAccountListDto> GetListBillAccounts()
        {

            var billAccountList = _billAccountsRepository.GetAll().Distinct().ToList();
            return new ListResultDto<BillAccountListDto>(billAccountList.MapTo<List<BillAccountListDto>>());
        }
        /// <summary>
        /// 获取辅助核算 
        /// </summary>
        /// <param name="input">项目：1;客户：2;人员：3</param>
        /// <returns></returns>
        public ListResultDto<OtherCheckListDto> GetListOtherChecks(int input)
        {

            var otherCheckList = _otherChecksRepository.GetAll().Where(x => x.CheckTypeId == input).ToList();
            return new ListResultDto<OtherCheckListDto>(otherCheckList.MapTo<List<OtherCheckListDto>>());
        }
        #region 辅助核算
        public async Task<ListResultDto<OtherCheckListDto>> GetBillOtherChecks(GetOtherChecksInput input)
        {
            var query = _otherChecksRepository.GetAll()
                .WhereIf(
                    !input.Filter.IsNullOrWhiteSpace(),
                    t =>
                        t.CheckName.Contains(input.Filter) ||
                        t.Remark.Contains(input.Filter)
                );
            var dataCount = await query.CountAsync();
            var data = await query.OrderBy(input.Sorting).PageBy(input).ToListAsync();

            return new PagedResultDto<OtherCheckListDto>(
                dataCount,
                data.MapTo<List<OtherCheckListDto>>()
                );
        }

        #region 根据Guid获取数据对象
        /// <summary>
        /// 新增、编辑页面中获取对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateOtherCheck, AppPermissions.Pages_FinanceModule_DataMaintains_EditOtherCheck)]
        public async Task<GetOtherCheckForEditOutput> GetBillOtherCheckForEdit(NullableIdDto<Guid> input)
        {
            var output = new GetOtherCheckForEditOutput
            {

            };

            if (!input.Id.HasValue)
            {
                //Creating a new object
                output.OtherCheck = new OtherCheckEditDto();
            }
            else
            {
                //Editing an existing object
                var existingObject = await _otherChecksRepository.GetAsync(input.Id.Value);

                output.OtherCheck = existingObject.MapTo<OtherCheckEditDto>();
            }

            return output;
        }
        #endregion

        #region 新增、编辑对象，带权限检查
        /// <summary>
        /// 新增、编辑对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateOtherCheck, AppPermissions.Pages_FinanceModule_DataMaintains_EditOtherCheck)]
        public async Task<BillOtherCheck> CreateOrUpdateOtherCheck(CreateOrUpdateOtherCheckInput input)
        {
            if (input.OtherCheck.Id.HasValue)
            {
                return await UpdateOtherCheck(input);
            }
            else
            {
                return await CreateOtherCheck(input);
            }
        }

        /// <summary>
        /// 新增对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_CreateOtherCheck)]
        protected virtual async Task<BillOtherCheck> CreateOtherCheck(CreateOrUpdateOtherCheckInput input)
        {
            var o = input.OtherCheck.MapTo<BillOtherCheck>();


            return await _otherChecksRepository.InsertAsync(o);
        }
        /// <summary>
        /// 编辑对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_EditOtherCheck)]
        protected virtual async Task<BillOtherCheck> UpdateOtherCheck(CreateOrUpdateOtherCheckInput input)
        {
            Debug.Assert(input.OtherCheck.Id != null, "input.BillOtherCheck.Id should be set.");

            var o = await _otherChecksRepository.GetAsync(input.OtherCheck.Id.Value);
            //Update classroom properties
            input.OtherCheck.MapTo(o);
            return await _otherChecksRepository.UpdateAsync(o);
        }
        #endregion

        #region 删除辅助核算数据，带权限检查
        /// <summary>
        /// 删除对象，带权限检查。
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        [AbpAuthorize(AppPermissions.Pages_FinanceModule_DataMaintains_DeleteOtherCheck)]
        public async Task DeleteOtherCheck(EntityDto<Guid> input)
        {
            var o = await _otherChecksRepository.GetAsync(input.Id);
            await _otherChecksRepository.DeleteAsync(o);
        }
        #endregion
        #endregion
    }
}
